package xin.clips.web.controller.gy;

import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.JSONArray;
import com.alibaba.fastjson.JSONObject;
import com.sun.jna.platform.unix.solaris.LibKstat;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
import xin.clips.common.annotation.VisistLog;
import xin.clips.common.core.controller.BaseController;
import xin.clips.common.core.domain.AjaxResult;
import xin.clips.common.core.domain.entity.SysDictData;
import xin.clips.common.enums.gy.DeviceStatusEnum;
import xin.clips.common.enums.gy.DeviceTypeEnum;
import xin.clips.common.utils.DictUtils;
import xin.clips.common.utils.StringUtils;
import xin.clips.system.domain.SysLogininfor;
import xin.clips.system.domain.SysVisitLog;
import xin.clips.system.domain.gy.*;
import xin.clips.system.dto.*;
import xin.clips.system.mapper.gy.GyMachineDayRuntimeMapper;
import xin.clips.system.service.ISysDictDataService;
import xin.clips.system.service.ISysLogininforService;
import xin.clips.system.service.ISysVisitLogService;
import xin.clips.system.service.gy.IGyArmParamService;
import xin.clips.system.service.gy.IGyDeviceService;
import xin.clips.system.service.gy.IGyMachineParamService;

import java.time.LocalDate;
import java.time.format.DateTimeFormatter;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

@RestController
@RequestMapping("/app")
public class AppController extends BaseController {

    private static final Logger log = LoggerFactory.getLogger(AppController.class);

    @Autowired
    private ISysDictDataService dictDataService;

    @Autowired
    private IGyDeviceService deviceService;

    @Autowired
    private IGyArmParamService armParamService;

    @Autowired
    private IGyMachineParamService machineParamService;

    @Autowired
    private GyMachineDayRuntimeMapper machineDayRuntimeMapper;



    /**
     * 设备状态显示数据
     *
     * @return
     */
    @RequestMapping(value = "/getDeviceStatusCountData")
    public AjaxResult deviceStatusCountByLocations() {

        //查询所有的学院，根据学院分类汇总
        SysDictData typeDictData = new SysDictData();
        typeDictData.setDictType("gy_locations");      //设备类型

        SysDictData statusDictData = new SysDictData();
        statusDictData.setDictType("gy_device_status");  //设备状态
        List<SysDictData> statusDicts = dictDataService.selectDictDataList(statusDictData);

        List<SysDictData> locationsData = dictDataService.selectDictDataList(typeDictData);
        List<DeviceStatusCountByLocationsDTO> list = new ArrayList<>();
        for (SysDictData dictData : locationsData) {
            Integer locationId = Integer.parseInt(dictData.getDictValue());
            DeviceStatusCountByLocationsDTO deviceStatusCountByLocationsDTO = new DeviceStatusCountByLocationsDTO();
            for (SysDictData status : statusDicts) {
                GyDevice gyDevice = new GyDevice();
                gyDevice.setLocationId(locationId);
                deviceStatusCountByLocationsDTO.setId(String.valueOf(locationId));
                gyDevice.setDeviceStatus(Integer.parseInt(status.getDictValue()));
                Integer count = deviceService.selectDeviceStatusCountByLocations(gyDevice);
                if (status.getDictValue().equals(DeviceStatusEnum.NORMAL.getCode().toString())) {  //正常
                    deviceStatusCountByLocationsDTO.setNormal(String.valueOf(count));
                } else if (status.getDictValue().equals(DeviceStatusEnum.WARNING.getCode().toString())) {  //告警
                    deviceStatusCountByLocationsDTO.setWarning(String.valueOf(count));
                } else if (status.getDictValue().equals(DeviceStatusEnum.ERROR.getCode().toString())) { //预警
                    deviceStatusCountByLocationsDTO.setError(String.valueOf(count));
                } else if (status.getDictValue().equals(DeviceStatusEnum.OFFLINE.getCode().toString())) {  //离线
                    deviceStatusCountByLocationsDTO.setOffline(String.valueOf(count));
                }
            }
            list.add(deviceStatusCountByLocationsDTO);
        }
        return AjaxResult.success(list);
    }


    /**
     * 示例返回报文：
     * <p>
     * 设备种类分布统计数据
     *
     * @return
     */
    @RequestMapping(value = "/getDeviceStatusDistributeData")
    public AjaxResult deviceStatusDistribute() {
        //查询所有的学院，根据学院分类汇总
        SysDictData typeDictData = new SysDictData();
        typeDictData.setDictType("gy_locations");      //设备类型
        SysDictData statusDictData = new SysDictData();
        statusDictData.setDictType("gy_device_type");  //设备状态
        List<SysDictData> typeDicts = dictDataService.selectDictDataList(statusDictData);
        List<SysDictData> locationsData = dictDataService.selectDictDataList(typeDictData);
        List<DeviceStatusDistributeDTO> data = new ArrayList<DeviceStatusDistributeDTO>();
        List<NameValueDataDTO> typeDatas = null;
        for (SysDictData dictData : locationsData) {
            DeviceStatusDistributeDTO deviceStatusDistributeDTO = new DeviceStatusDistributeDTO();
            Integer locationId = Integer.parseInt(dictData.getDictValue());
            deviceStatusDistributeDTO.setId(dictData.getDictValue());
            NameValueDataDTO nameValueDataDTO = null;
            typeDatas = new ArrayList<>();
            for (SysDictData type : typeDicts) {

                nameValueDataDTO = new NameValueDataDTO();
                GyDevice gyDevice = new GyDevice();
                gyDevice.setLocationId(locationId);
                gyDevice.setDeviceType(Integer.parseInt(type.getDictValue()));
                Integer count = deviceService.selectDeviceStatusDistributeByLocations(gyDevice);
                if (type.getDictValue().equals(DeviceTypeEnum.ARM.getCode().toString())) {  //机械臂
                    nameValueDataDTO.setName(DeviceTypeEnum.ARM.getInfo());
                    nameValueDataDTO.setValue(String.valueOf(count));
                } else if (type.getDictValue().equals(DeviceTypeEnum.MACHINE.getCode().toString())) {  //冲压机床
                    nameValueDataDTO.setName(DeviceTypeEnum.MACHINE.getInfo());
                    nameValueDataDTO.setValue(String.valueOf(count));
                }
                typeDatas.add(nameValueDataDTO);
            }

            deviceStatusDistributeDTO.setData(typeDatas);
            data.add(deviceStatusDistributeDTO);
        }
        return AjaxResult.success(data);
    }


    /**
     * 实时报警数据
     *
     * @return
     */
    @RequestMapping(value = "/getAlarmRecord")
    public AjaxResult getAlarmRecord() {
        return AjaxResult.success(deviceService.selectDeviceStatusRecord(new GyDevice()));
    }

    /**
     * 设备状态趋势统计数据
     * <p>
     * {
     * "catalog": ["搬运机器⼈", "CNC设备", "打磨机器⼈", "巡检机器⼈", "焊接机器⼈",
     * "滚筒机器⼈"], // 设备类别
     * "data": [{
     * "name": "正常",
     * "data": [5, 20, 36, 10, 10, 20]
     * }, {
     * "name": "预警",
     * "data": [15, 120, 36, 20, 210, 20]
     * }, {
     * "name": "异常",
     * "data": [35, 120, 316, 10, 110, 20]
     * }, {
     * "name": "离线",
     * "data": [115, 120, 136, 10, 10, 20]}]
     * }
     */
    @RequestMapping(value = "/getDeviceStatusTrendData")
    public AjaxResult getDeviceStatusTrendData() {
        Map<String, Object> map = new HashMap();

        // List<List<DeviceTypeStatusCountDTO> > deviceTypeDataDTOS = new ArrayList<>();
        //  List<DeviceTypeStatusCountDTO>  datas= null;

        SysDictData typeDictData = new SysDictData();
        typeDictData.setDictType("gy_device_type");      //设备类型
        List<SysDictData> typeDicts = dictDataService.selectDictDataList(typeDictData);
        SysDictData statusDictData = new SysDictData();
        statusDictData.setDictType("gy_device_status");  //设备状态
        List<SysDictData> statusDicts = dictDataService.selectDictDataList(statusDictData);
        List<String> typeList = new ArrayList<>();
        for (SysDictData typeData : typeDicts) {
            typeList.add(typeData.getDictLabel());
        }
        List<String> statusList = new ArrayList<>();
        List<GyDeviceStatusDataDTO> gyDeviceStatusDatumDTOS = new ArrayList<>();
        for (SysDictData statusData : statusDicts) {
            statusList.add(statusData.getDictLabel());
            GyDeviceStatusDataDTO gyDeviceStatusDataDTO = new GyDeviceStatusDataDTO();
            gyDeviceStatusDataDTO.setName(statusData.getDictLabel());
            gyDeviceStatusDatumDTOS.add(gyDeviceStatusDataDTO);
        }
        List<ArrayList> list = new ArrayList();

        for (SysDictData statusData : statusDicts) {
            ArrayList temp = new ArrayList();
            for (SysDictData type : typeDicts) {
                GyDevice device = new GyDevice();
                device.setDeviceType(Integer.parseInt(type.getDictValue()));
                device.setDeviceStatus(Integer.parseInt(statusData.getDictValue()));
                Integer total = deviceService.selectGyDeviceByDeviceTypeAndStatus(device);//根据设备类型，状态
                temp.add(total.toString());
            }
            list.add(temp);
        }
        map.put("catalog", typeList.toArray());  //类型组装['打磨机器人', '机械臂', '巡检机器人', '冲压机床', '数控机床']
        JSONArray jsonArray = new JSONArray();
        for (int i = 0; i < list.size(); i++) {
            JSONObject stObject = new JSONObject();
            stObject.put("name", statusList.get(i));
            stObject.put("data", list.get(i).stream().toArray());
            jsonArray.add(stObject);
        }
        map.put("data", jsonArray);
        return AjaxResult.success(map);
    }


    /**
     * 设备种类数据为列表数据，
     * <p>
     * [
     * {
     * "name": "搬运机器⼈", // 设备种类名称
     * "value": 12 // 设备种类数据
     * }
     * ]
     */
    @RequestMapping(value = "/selectDeviceTypeCountData")
    public AjaxResult selectDeviceTypeCountData() {
        return AjaxResult.success(deviceService.selectDeviceTypeCountRecord(new GyDevice()));
    }

    /**
     * 设备预警信息数据，
     * <p>
     * [
     * {
     * "name": "搬运机器⼈", // 设备种类名称
     * "value": 12 // 设备种类数据
     * }
     * ]
     */
    @RequestMapping(value = "/selectDeviceAlarmData")
    public AjaxResult selectDeviceAlarmData() {
        return AjaxResult.success(deviceService.selectDeviceAlarmRecord(new GyDevice()));
    }


    /**
     * 学院设备状态数据，
     * "normal": 12, // 在线数量
     * "warning": 34, // 预警数量
     * "error": 4, // 故障数量
     * "offline": 40 // 离线数量
     */
    @RequestMapping(value = "/selectDeviceAlarmData/{locationId}")
    public AjaxResult selectDeviceStatusTotalByLocationId(@PathVariable("locationId") String locationId) {
        if (StringUtils.isEmpty(locationId)) {
            return AjaxResult.error("请传递学院id");
        }
        GyDevice gyDevice = new GyDevice();
        gyDevice.setLocationId(Integer.parseInt(locationId));
        List<Map> list = deviceService.selectDeviceStatusTotalByLocationId(gyDevice);
        DeviceTypeStatusCountDTO countDTO = new DeviceTypeStatusCountDTO();

        countDTO.setNormal(list.get(0).get("count").toString());
        countDTO.setWarning(list.get(1).get("count").toString());
        countDTO.setOffline(list.get(2).get("count").toString());
        countDTO.setError(list.get(3).get("count").toString());

        return AjaxResult.success(countDTO);
    }

    /**
     * 根据学院编号查询学院下面的设备状态统计数据
     * {
     * "msg": "操作成功",
     * "code": 0,
     * "data": [
     * {
     * "name": "211",
     * "type": "机械臂",
     * "status": "告警",
     * "timer": "0",
     * "id": "17"
     * },
     * {
     * "name": "威龙一号",
     * "type": "机械臂",
     * "status": "告警",
     * "timer": "0",
     * "id": "22"
     * }
     * ]
     * }
     */
    @RequestMapping(value = "/selectAlarmRecordByLocationId/{locationId}")
    public AjaxResult selectAlarmRecordByLocationId(@PathVariable("locationId") String locationId) {
        if (StringUtils.isEmpty(locationId)) {
            return AjaxResult.error("请传递学院id");
        }
        GyDevice gyDevice = new GyDevice();
        gyDevice.setDeviceStatus(DeviceStatusEnum.WARNING.getCode());
        gyDevice.setLocationId(Integer.parseInt(locationId));
        List<DeviceAlarmRecordDTO> deviceAlarmRecordDTOS = deviceService.selectAlarmRecordByLocationId(gyDevice);
        for (DeviceAlarmRecordDTO alarmRecord :
                deviceAlarmRecordDTOS) {
            if (alarmRecord.getType().equals(DeviceTypeEnum.MACHINE.getCode())) {
                alarmRecord.setTimer(machineParamService.
                        selectGyMachineParamByMachineId(Long.parseLong(alarmRecord.getId())).getRunTime());
            }
        }

        return AjaxResult.success(deviceAlarmRecordDTOS);
    }

    /**
     * 学院下面所有的设备集合
     */
    @RequestMapping(value = "/selectDevicesByLocationId/{locationId}")
    public AjaxResult selectDevicesByLocationId(@PathVariable("locationId") String locationId) {

        if (StringUtils.isEmpty(locationId)) {
            return AjaxResult.error("请传递学院id");
        }
        GyDevice gyDevice = new GyDevice();
        gyDevice.setLocationId(Integer.parseInt(locationId));
        return AjaxResult.success(deviceService.selectDevicesByLocationId(gyDevice));
    }

    /**
     * 学院下面所有设备详情
     */
    @RequestMapping(value = "/selectGyDeviceDetail/{locationId}/{id}")
    public AjaxResult selectDevicesByLocationId(@PathVariable("locationId") String locationId, @PathVariable("id") String id) {

        if (StringUtils.isEmpty(locationId)) {
            return AjaxResult.error("请传递学院id");
        }
        if (StringUtils.isEmpty(id)) {
            return AjaxResult.error("请传递设备id");
        }

        GyDevice gyDevice = new GyDevice();
        gyDevice.setLocationId(Integer.parseInt(locationId));
        gyDevice.setDeviceId(Long.parseLong(id));
        List<GyDevice> devices = deviceService.selectGyDeviceList(gyDevice);
        gyDevice = devices.get(0);
        String deviceType = gyDevice.getDeviceType().toString();
        if (deviceType.equals(DeviceTypeEnum.ARM.getCode().toString())) {
            ArmParamDTO armParam = armParamService.selectDpGyArmParamByDeviceId(gyDevice.getDeviceId());
            return AjaxResult.success(armParam);
        } else if (deviceType.equals(DeviceTypeEnum.MACHINE.getCode().toString())) {
            MachineParamDTO machineParam = machineParamService.selectDpGyMachineParamByDeviceId(gyDevice.getDeviceId());
            return AjaxResult.success(machineParam);
        }
        return AjaxResult.error("设备类型不匹配，请联系管理员.");
    }

    /**
     * 字典查询
     *
     * @return
     */
    @RequestMapping(value = "/dict/{type}")
    public AjaxResult getAlarmRecord(@PathVariable("type") String type) {
        List<SysDictData> dictData = DictUtils.getDictCache(type);
        return AjaxResult.success("", dictData);
    }

    /**
     * -------------------other
     *
     * @return
     */
//    @RequestMapping(value = "/login")
//    public AjaxResult login() {
//        Map<String, String> loginDayMap = new HashMap<>(); //登录量 每日统计数据，key是日期，value是值，默认值是0.
//        Map<String, String> visitDayMap = new HashMap<>(); //访问量 每日统计数据，key是日期，value是值，默认值是0.
//        List<String> dateList = new ArrayList<>();
//        String startTime = loginDayMap.get(6);
//        String endTime = loginDayMap.get(0);
//        for (int i = 7; i >= 0; i--) {
//            String date = LocalDate.now().minusDays(i).format(DateTimeFormatter.ofPattern("yyyy-MM-dd"));
//            if (i == 7) {
//                startTime = date;
//            }
//            if (i == 0) {
//                endTime = date;
//            }
//            dateList.add(date);
//            loginDayMap.put(date, "0");
//            visitDayMap.put(date, "0");
//        }
//        SysLogininfor logininfor = new SysLogininfor();
//        logininfor.getParams().put("beginTime", startTime + " 00:00:00");
//        logininfor.getParams().put("endTime", endTime + " 23:59:59");
//
//        List<SysLogininfor> logininfors = logininforService.selectLoginDayAnalyByTime(logininfor);
//        for (SysLogininfor loginInfo : logininfors) {
//            loginDayMap.put(loginInfo.getDat(), loginInfo.getCount()); //将取到的数据覆盖初始的
//        }
//        ArrayList<String> dayLoginCountArray = new ArrayList<>();
//        for (String date : dateList) {
//            dayLoginCountArray.add(loginDayMap.get(date)); //将值转换为string集合。
//        }
//
//        //日期访问量统计
//        SysVisitLog sysVisitLog = new SysVisitLog();
//        sysVisitLog.getParams().put("beginTime", startTime + " 00:00:00");
//        sysVisitLog.getParams().put("endTime", endTime + " 23:59:59");
//
//        List<SysVisitLog> sysVisitLogs = visitLogService.selectVisitDayAnalyByTime(sysVisitLog);
//
//        for (SysVisitLog visitLog : sysVisitLogs) {
//            visitDayMap.put(visitLog.getDat(), visitLog.getCount()); //将取到的数据覆盖初始的
//        }
//
//        ArrayList<String> dayVisitCountArray = new ArrayList<>();
//        for (String date : dateList) {
//            dayVisitCountArray.add(visitDayMap.get(date)); //将值转换为string集合。
//        }
//
//        AjaxResult ajaxResult = new AjaxResult();
//        ajaxResult.put("dayLoginCountArray", dayLoginCountArray);  //登录量[]
//        ajaxResult.put("rqArray", dateList);//日期array
//        ajaxResult.put("dayVisitCountArray", dayVisitCountArray); //访问量[]
//        return ajaxResult;
//    }

//    /**
//     * -------------------other
//     *
//     * @return
//     */
//    @RequestMapping(value = "/visitTop3")
//    public AjaxResult visitTop3() {
//        SysVisitLog visistLog = new SysVisitLog();
//        List<SysVisitLog> sceneData = visitLogService.selectVisitTop3(visistLog);  //主扫码top统计
//        List<String> keyData = new ArrayList();
//        List<String> valueData = new ArrayList();
//        for (SysVisitLog temp : sceneData) {
//            keyData.add(temp.getDat());
//            valueData.add(temp.getCount());
//        }
//        AjaxResult ajaxResult = new AjaxResult();
//        ajaxResult.put("keyData", keyData.toArray());
//        ajaxResult.put("valueData", valueData.toArray());
//        return ajaxResult;
//    }

    /**
     * 设备运行时间
     *
     * @return
     */
    @RequestMapping(value = "/getDeviceRuntime")
    public AjaxResult getDeviceRuntime(Integer locationId) {
        List<GyMachineDayRuntime> list = machineDayRuntimeMapper.getMachineDayRuntime(locationId);
        HashMap<String, List<GyMachineDayRuntime>> map = new HashMap<>();
        list.forEach(e -> {
            e.setRunTime((Integer.parseInt(e.getRunTime())/60)+""); //秒转为分钟
            if(map.containsKey(e.getDeviceName())){
                List<GyMachineDayRuntime> deviceList = map.get(e.getDeviceName());
                deviceList.add(e);
                map.put(e.getDeviceName(),deviceList);
            } else {
                List<GyMachineDayRuntime> deviceList = new ArrayList<>();
                deviceList.add(e);
                map.put(e.getDeviceName(),deviceList);
            }
        });

        return AjaxResult.success(map);

    }

    /**
     * 设备产量
     *
     * @return
     */
    @RequestMapping(value = "/getDeviceProduction")
    public AjaxResult getDeviceProduction(Integer locationId) {
        List<GyMachineDayProduction> list = machineDayRuntimeMapper.getMachineDayProduction(locationId);
        HashMap<String, List<GyMachineDayProduction>> map = new HashMap<>();
        list.forEach(e -> {
            if(map.containsKey(e.getDeviceName())){
                List<GyMachineDayProduction> deviceList = map.get(e.getDeviceName());
                deviceList.add(e);
                map.put(e.getDeviceName(),deviceList);
            } else {
                List<GyMachineDayProduction> deviceList = new ArrayList<>();
                deviceList.add(e);
                map.put(e.getDeviceName(),deviceList);
            }
        });

        return AjaxResult.success(map);

    }
}
